package org.ymh.unix_file_system.dao;

import com.fasterxml.jackson.core.JsonProcessingException;
import com.fasterxml.jackson.core.type.TypeReference;
import com.fasterxml.jackson.databind.ObjectMapper;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Repository;
import org.ymh.unix_file_system.domain.*;

import java.io.File;
import java.io.IOException;
import java.nio.file.Path;
import java.nio.file.Paths;
import java.util.ArrayList;
import java.util.LinkedList;
import java.util.List;

/**
 * @author lenovo
 * @version 1.0
 * @description: TODO
 * @date 2023/12/17 1:54
 */
@Repository
public class JsonDataOperate {

    @Autowired
    public GlobalVariable globalVariable;
    /**
    * @Description json的序列化，转化为对象
    * @Author  lenovo
    * @Date   2023/12/17 16:40
    * @Param
    * @Return
    * @Exception
    */

    public <T> T jsonFileParse(Object value,String path)
    {
        Path paths= Paths.get(globalVariable.foundation.blocksPath);
        paths=paths.resolve("#"+path+".json");
        System.out.println(paths);
        File file = paths.toFile();
        try {
            if(value instanceof SuperBlock)
                return (T) new ObjectMapper().readValue(file, SuperBlock.class);
            else if(value instanceof boolean[])
                return (T) new ObjectMapper().readValue(file, new TypeReference<boolean[]>() {
                });
            else if(value instanceof DirNode)
                return (T) new ObjectMapper().readValue(file, DirNode.class);
            else if(value instanceof INode[])
                return (T) new ObjectMapper().readValue(file, new TypeReference<INode[]>() {
                });
            else if(value instanceof FreeBlockLinkedList)
                return (T) new ObjectMapper().readValue(file, new TypeReference<FreeBlockLinkedList>() {
                });
            else if(value instanceof LinkedList<?>)
                return (T) new ObjectMapper().readValue(file, new TypeReference<LinkedList>() {
                });
            else if(value instanceof ArrayList<?>)
                return (T) new ObjectMapper().readValue(file, new TypeReference<ArrayList>() {
                });
            else {
                return null;
            }
        } catch (IOException e) {
            throw new RuntimeException(e);
        }
    }
    /**
    * @Description  写json，反序列列并写入文件(普通权限,会屏蔽写超级块）
    * @Author  lenovo
    * @Date   2023/12/17 16:40
    * @Param
    * @Return
    * @Exception
    */

    public <T> void jsonFileStringify(T value,String[] path)
    {
        for(int i=globalVariable.foundation.superBlockStart;i<globalVariable.foundation.superBlockStart+globalVariable.foundation.superBlockCount;i++)
        {
            if(path[0].equals(i+""))
            {
                return;//屏蔽对超级块的写
            }
        }
        Path paths= Paths.get(globalVariable.foundation.blocksPath);
        for (int i = 0; i < path.length; i++) {

            Path tempPath=paths.resolve("#"+path[i]+".json");
            File file = tempPath.toFile();
            try {
                if(i==0) {//第一个物理块写入json
                    new ObjectMapper().writeValue(file, value);
                }
                else{//其他的乱写
                    new ObjectMapper().writeValue(file, "该物理块已占据");
                }
            } catch (IOException e) {
                throw new RuntimeException(e);
            }
        }
    }
    public <T> void superJsonFileStringify(T value,String[] path)
    {
        Path paths= Paths.get(globalVariable.foundation.blocksPath);
        for (int i = 0; i < path.length; i++) {
            Path tempPath=paths.resolve("#"+path[i]+".json");
            File file = tempPath.toFile();
            try {
                if(i==0) {//第一个物理块写入json
                    new ObjectMapper().writeValue(file, value);
                }
                else{//其他的乱写
                    new ObjectMapper().writeValue(file, "该物理块已占据");
                }
            } catch (IOException e) {
                throw new RuntimeException(e);
            }
        }
    }
    public String toJson(Object object)
    {
        try {
            return new ObjectMapper().writeValueAsString(object);
        } catch (JsonProcessingException e) {
            throw new RuntimeException(e);
        }
    }

}
